home *** CD-ROM | disk | FTP | other *** search
/ Clickx 115 / Clickx 115.iso / software / tools / windows / tails-i386-0.16.iso / live / filesystem.squashfs / usr / lib / python2.6 / httplib.py < prev    next >
Encoding:
Python Source  |  2010-12-26  |  44.4 KB  |  1,344 lines

  1. """HTTP/1.1 client library
  2.  
  3. <intro stuff goes here>
  4. <other stuff, too>
  5.  
  6. HTTPConnection goes through a number of "states", which define when a client
  7. may legally make another request or fetch the response for a particular
  8. request. This diagram details these state transitions:
  9.  
  10.     (null)
  11.       |
  12.       | HTTPConnection()
  13.       v
  14.     Idle
  15.       |
  16.       | putrequest()
  17.       v
  18.     Request-started
  19.       |
  20.       | ( putheader() )*  endheaders()
  21.       v
  22.     Request-sent
  23.       |
  24.       | response = getresponse()
  25.       v
  26.     Unread-response   [Response-headers-read]
  27.       |\____________________
  28.       |                     |
  29.       | response.read()     | putrequest()
  30.       v                     v
  31.     Idle                  Req-started-unread-response
  32.                      ______/|
  33.                    /        |
  34.    response.read() |        | ( putheader() )*  endheaders()
  35.                    v        v
  36.        Request-started    Req-sent-unread-response
  37.                             |
  38.                             | response.read()
  39.                             v
  40.                           Request-sent
  41.  
  42. This diagram presents the following rules:
  43.   -- a second request may not be started until {response-headers-read}
  44.   -- a response [object] cannot be retrieved until {request-sent}
  45.   -- there is no differentiation between an unread response body and a
  46.      partially read response body
  47.  
  48. Note: this enforcement is applied by the HTTPConnection class. The
  49.       HTTPResponse class does not enforce this state machine, which
  50.       implies sophisticated clients may accelerate the request/response
  51.       pipeline. Caution should be taken, though: accelerating the states
  52.       beyond the above pattern may imply knowledge of the server's
  53.       connection-close behavior for certain requests. For example, it
  54.       is impossible to tell whether the server will close the connection
  55.       UNTIL the response headers have been read; this means that further
  56.       requests cannot be placed into the pipeline until it is known that
  57.       the server will NOT be closing the connection.
  58.  
  59. Logical State                  __state            __response
  60. -------------                  -------            ----------
  61. Idle                           _CS_IDLE           None
  62. Request-started                _CS_REQ_STARTED    None
  63. Request-sent                   _CS_REQ_SENT       None
  64. Unread-response                _CS_IDLE           <response_class>
  65. Req-started-unread-response    _CS_REQ_STARTED    <response_class>
  66. Req-sent-unread-response       _CS_REQ_SENT       <response_class>
  67. """
  68.  
  69. from array import array
  70. import socket
  71. from sys import py3kwarning
  72. from urlparse import urlsplit
  73. import warnings
  74. with warnings.catch_warnings():
  75.     if py3kwarning:
  76.         warnings.filterwarnings("ignore", ".*mimetools has been removed",
  77.                                 DeprecationWarning)
  78.     import mimetools
  79.  
  80. try:
  81.     from cStringIO import StringIO
  82. except ImportError:
  83.     from StringIO import StringIO
  84.  
  85. __all__ = ["HTTP", "HTTPResponse", "HTTPConnection",
  86.            "HTTPException", "NotConnected", "UnknownProtocol",
  87.            "UnknownTransferEncoding", "UnimplementedFileMode",
  88.            "IncompleteRead", "InvalidURL", "ImproperConnectionState",
  89.            "CannotSendRequest", "CannotSendHeader", "ResponseNotReady",
  90.            "BadStatusLine", "error", "responses"]
  91.  
  92. HTTP_PORT = 80
  93. HTTPS_PORT = 443
  94.  
  95. _UNKNOWN = 'UNKNOWN'
  96.  
  97. # connection states
  98. _CS_IDLE = 'Idle'
  99. _CS_REQ_STARTED = 'Request-started'
  100. _CS_REQ_SENT = 'Request-sent'
  101.  
  102. # status codes
  103. # informational
  104. CONTINUE = 100
  105. SWITCHING_PROTOCOLS = 101
  106. PROCESSING = 102
  107.  
  108. # successful
  109. OK = 200
  110. CREATED = 201
  111. ACCEPTED = 202
  112. NON_AUTHORITATIVE_INFORMATION = 203
  113. NO_CONTENT = 204
  114. RESET_CONTENT = 205
  115. PARTIAL_CONTENT = 206
  116. MULTI_STATUS = 207
  117. IM_USED = 226
  118.  
  119. # redirection
  120. MULTIPLE_CHOICES = 300
  121. MOVED_PERMANENTLY = 301
  122. FOUND = 302
  123. SEE_OTHER = 303
  124. NOT_MODIFIED = 304
  125. USE_PROXY = 305
  126. TEMPORARY_REDIRECT = 307
  127.  
  128. # client error
  129. BAD_REQUEST = 400
  130. UNAUTHORIZED = 401
  131. PAYMENT_REQUIRED = 402
  132. FORBIDDEN = 403
  133. NOT_FOUND = 404
  134. METHOD_NOT_ALLOWED = 405
  135. NOT_ACCEPTABLE = 406
  136. PROXY_AUTHENTICATION_REQUIRED = 407
  137. REQUEST_TIMEOUT = 408
  138. CONFLICT = 409
  139. GONE = 410
  140. LENGTH_REQUIRED = 411
  141. PRECONDITION_FAILED = 412
  142. REQUEST_ENTITY_TOO_LARGE = 413
  143. REQUEST_URI_TOO_LONG = 414
  144. UNSUPPORTED_MEDIA_TYPE = 415
  145. REQUESTED_RANGE_NOT_SATISFIABLE = 416
  146. EXPECTATION_FAILED = 417
  147. UNPROCESSABLE_ENTITY = 422
  148. LOCKED = 423
  149. FAILED_DEPENDENCY = 424
  150. UPGRADE_REQUIRED = 426
  151.  
  152. # server error
  153. INTERNAL_SERVER_ERROR = 500
  154. NOT_IMPLEMENTED = 501
  155. BAD_GATEWAY = 502
  156. SERVICE_UNAVAILABLE = 503
  157. GATEWAY_TIMEOUT = 504
  158. HTTP_VERSION_NOT_SUPPORTED = 505
  159. INSUFFICIENT_STORAGE = 507
  160. NOT_EXTENDED = 510
  161.  
  162. # Mapping status codes to official W3C names
  163. responses = {
  164.     100: 'Continue',
  165.     101: 'Switching Protocols',
  166.  
  167.     200: 'OK',
  168.     201: 'Created',
  169.     202: 'Accepted',
  170.     203: 'Non-Authoritative Information',
  171.     204: 'No Content',
  172.     205: 'Reset Content',
  173.     206: 'Partial Content',
  174.  
  175.     300: 'Multiple Choices',
  176.     301: 'Moved Permanently',
  177.     302: 'Found',
  178.     303: 'See Other',
  179.     304: 'Not Modified',
  180.     305: 'Use Proxy',
  181.     306: '(Unused)',
  182.     307: 'Temporary Redirect',
  183.  
  184.     400: 'Bad Request',
  185.     401: 'Unauthorized',
  186.     402: 'Payment Required',
  187.     403: 'Forbidden',
  188.     404: 'Not Found',
  189.     405: 'Method Not Allowed',
  190.     406: 'Not Acceptable',
  191.     407: 'Proxy Authentication Required',
  192.     408: 'Request Timeout',
  193.     409: 'Conflict',
  194.     410: 'Gone',
  195.     411: 'Length Required',
  196.     412: 'Precondition Failed',
  197.     413: 'Request Entity Too Large',
  198.     414: 'Request-URI Too Long',
  199.     415: 'Unsupported Media Type',
  200.     416: 'Requested Range Not Satisfiable',
  201.     417: 'Expectation Failed',
  202.  
  203.     500: 'Internal Server Error',
  204.     501: 'Not Implemented',
  205.     502: 'Bad Gateway',
  206.     503: 'Service Unavailable',
  207.     504: 'Gateway Timeout',
  208.     505: 'HTTP Version Not Supported',
  209. }
  210.  
  211. # maximal amount of data to read at one time in _safe_read
  212. MAXAMOUNT = 1048576
  213.  
  214. class HTTPMessage(mimetools.Message):
  215.  
  216.     def addheader(self, key, value):
  217.         """Add header for field key handling repeats."""
  218.         prev = self.dict.get(key)
  219.         if prev is None:
  220.             self.dict[key] = value
  221.         else:
  222.             combined = ", ".join((prev, value))
  223.             self.dict[key] = combined
  224.  
  225.     def addcontinue(self, key, more):
  226.         """Add more field data from a continuation line."""
  227.         prev = self.dict[key]
  228.         self.dict[key] = prev + "\n " + more
  229.  
  230.     def readheaders(self):
  231.         """Read header lines.
  232.  
  233.         Read header lines up to the entirely blank line that terminates them.
  234.         The (normally blank) line that ends the headers is skipped, but not
  235.         included in the returned list.  If a non-header line ends the headers,
  236.         (which is an error), an attempt is made to backspace over it; it is
  237.         never included in the returned list.
  238.  
  239.         The variable self.status is set to the empty string if all went well,
  240.         otherwise it is an error message.  The variable self.headers is a
  241.         completely uninterpreted list of lines contained in the header (so
  242.         printing them will reproduce the header exactly as it appears in the
  243.         file).
  244.  
  245.         If multiple header fields with the same name occur, they are combined
  246.         according to the rules in RFC 2616 sec 4.2:
  247.  
  248.         Appending each subsequent field-value to the first, each separated
  249.         by a comma. The order in which header fields with the same field-name
  250.         are received is significant to the interpretation of the combined
  251.         field value.
  252.         """
  253.         # XXX The implementation overrides the readheaders() method of
  254.         # rfc822.Message.  The base class design isn't amenable to
  255.         # customized behavior here so the method here is a copy of the
  256.         # base class code with a few small changes.
  257.  
  258.         self.dict = {}
  259.         self.unixfrom = ''
  260.         self.headers = hlist = []
  261.         self.status = ''
  262.         headerseen = ""
  263.         firstline = 1
  264.         startofline = unread = tell = None
  265.         if hasattr(self.fp, 'unread'):
  266.             unread = self.fp.unread
  267.         elif self.seekable:
  268.             tell = self.fp.tell
  269.         while True:
  270.             if tell:
  271.                 try:
  272.                     startofline = tell()
  273.                 except IOError:
  274.                     startofline = tell = None
  275.                     self.seekable = 0
  276.             line = self.fp.readline()
  277.             if not line:
  278.                 self.status = 'EOF in headers'
  279.                 break
  280.             # Skip unix From name time lines
  281.             if firstline and line.startswith('From '):
  282.                 self.unixfrom = self.unixfrom + line
  283.                 continue
  284.             firstline = 0
  285.             if headerseen and line[0] in ' \t':
  286.                 # XXX Not sure if continuation lines are handled properly
  287.                 # for http and/or for repeating headers
  288.                 # It's a continuation line.
  289.                 hlist.append(line)
  290.                 self.addcontinue(headerseen, line.strip())
  291.                 continue
  292.             elif self.iscomment(line):
  293.                 # It's a comment.  Ignore it.
  294.                 continue
  295.             elif self.islast(line):
  296.                 # Note! No pushback here!  The delimiter line gets eaten.
  297.                 break
  298.             headerseen = self.isheader(line)
  299.             if headerseen:
  300.                 # It's a legal header line, save it.
  301.                 hlist.append(line)
  302.                 self.addheader(headerseen, line[len(headerseen)+1:].strip())
  303.                 continue
  304.             else:
  305.                 # It's not a header line; throw it back and stop here.
  306.                 if not self.dict:
  307.                     self.status = 'No headers'
  308.                 else:
  309.                     self.status = 'Non-header line where header expected'
  310.                 # Try to undo the read.
  311.                 if unread:
  312.                     unread(line)
  313.                 elif tell:
  314.                     self.fp.seek(startofline)
  315.                 else:
  316.                     self.status = self.status + '; bad seek'
  317.                 break
  318.  
  319. class HTTPResponse:
  320.  
  321.     # strict: If true, raise BadStatusLine if the status line can't be
  322.     # parsed as a valid HTTP/1.0 or 1.1 status line.  By default it is
  323.     # false because it prevents clients from talking to HTTP/0.9
  324.     # servers.  Note that a response with a sufficiently corrupted
  325.     # status line will look like an HTTP/0.9 response.
  326.  
  327.     # See RFC 2616 sec 19.6 and RFC 1945 sec 6 for details.
  328.  
  329.     def __init__(self, sock, debuglevel=0, strict=0, method=None):
  330.         self.fp = sock.makefile('rb', 0)
  331.         self.debuglevel = debuglevel
  332.         self.strict = strict
  333.         self._method = method
  334.  
  335.         self.msg = None
  336.  
  337.         # from the Status-Line of the response
  338.         self.version = _UNKNOWN # HTTP-Version
  339.         self.status = _UNKNOWN  # Status-Code
  340.         self.reason = _UNKNOWN  # Reason-Phrase
  341.  
  342.         self.chunked = _UNKNOWN         # is "chunked" being used?
  343.         self.chunk_left = _UNKNOWN      # bytes left to read in current chunk
  344.         self.length = _UNKNOWN          # number of bytes left in response
  345.         self.will_close = _UNKNOWN      # conn will close at end of response
  346.  
  347.     def _read_status(self):
  348.         # Initialize with Simple-Response defaults
  349.         line = self.fp.readline()
  350.         if self.debuglevel > 0:
  351.             print "reply:", repr(line)
  352.         if not line:
  353.             # Presumably, the server closed the connection before
  354.             # sending a valid response.
  355.             raise BadStatusLine(line)
  356.         try:
  357.             [version, status, reason] = line.split(None, 2)
  358.         except ValueError:
  359.             try:
  360.                 [version, status] = line.split(None, 1)
  361.                 reason = ""
  362.             except ValueError:
  363.                 # empty version will cause next test to fail and status
  364.                 # will be treated as 0.9 response.
  365.                 version = ""
  366.         if not version.startswith('HTTP/'):
  367.             if self.strict:
  368.                 self.close()
  369.                 raise BadStatusLine(line)
  370.             else:
  371.                 # assume it's a Simple-Response from an 0.9 server
  372.                 self.fp = LineAndFileWrapper(line, self.fp)
  373.                 return "HTTP/0.9", 200, ""
  374.  
  375.         # The status code is a three-digit number
  376.         try:
  377.             status = int(status)
  378.             if status < 100 or status > 999:
  379.                 raise BadStatusLine(line)
  380.         except ValueError:
  381.             raise BadStatusLine(line)
  382.         return version, status, reason
  383.  
  384.     def begin(self):
  385.         if self.msg is not None:
  386.             # we've already started reading the response
  387.             return
  388.  
  389.         # read until we get a non-100 response
  390.         while True:
  391.             version, status, reason = self._read_status()
  392.             if status != CONTINUE:
  393.                 break
  394.             # skip the header from the 100 response
  395.             while True:
  396.                 skip = self.fp.readline().strip()
  397.                 if not skip:
  398.                     break
  399.                 if self.debuglevel > 0:
  400.                     print "header:", skip
  401.  
  402.         self.status = status
  403.         self.reason = reason.strip()
  404.         if version == 'HTTP/1.0':
  405.             self.version = 10
  406.         elif version.startswith('HTTP/1.'):
  407.             self.version = 11   # use HTTP/1.1 code for HTTP/1.x where x>=1
  408.         elif version == 'HTTP/0.9':
  409.             self.version = 9
  410.         else:
  411.             raise UnknownProtocol(version)
  412.  
  413.         if self.version == 9:
  414.             self.length = None
  415.             self.chunked = 0
  416.             self.will_close = 1
  417.             self.msg = HTTPMessage(StringIO())
  418.             return
  419.  
  420.         self.msg = HTTPMessage(self.fp, 0)
  421.         if self.debuglevel > 0:
  422.             for hdr in self.msg.headers:
  423.                 print "header:", hdr,
  424.  
  425.         # don't let the msg keep an fp
  426.         self.msg.fp = None
  427.  
  428.         # are we using the chunked-style of transfer encoding?
  429.         tr_enc = self.msg.getheader('transfer-encoding')
  430.         if tr_enc and tr_enc.lower() == "chunked":
  431.             self.chunked = 1
  432.             self.chunk_left = None
  433.         else:
  434.             self.chunked = 0
  435.  
  436.         # will the connection close at the end of the response?
  437.         self.will_close = self._check_close()
  438.  
  439.         # do we have a Content-Length?
  440.         # NOTE: RFC 2616, S4.4, #3 says we ignore this if tr_enc is "chunked"
  441.         length = self.msg.getheader('content-length')
  442.         if length and not self.chunked:
  443.             try:
  444.                 self.length = int(length)
  445.             except ValueError:
  446.                 self.length = None
  447.             else:
  448.                 if self.length < 0:  # ignore nonsensical negative lengths
  449.                     self.length = None
  450.         else:
  451.             self.length = None
  452.  
  453.         # does the body have a fixed length? (of zero)
  454.         if (status == NO_CONTENT or status == NOT_MODIFIED or
  455.             100 <= status < 200 or      # 1xx codes
  456.             self._method == 'HEAD'):
  457.             self.length = 0
  458.  
  459.         # if the connection remains open, and we aren't using chunked, and
  460.         # a content-length was not provided, then assume that the connection
  461.         # WILL close.
  462.         if not self.will_close and \
  463.            not self.chunked and \
  464.            self.length is None:
  465.             self.will_close = 1
  466.  
  467.     def _check_close(self):
  468.         conn = self.msg.getheader('connection')
  469.         if self.version == 11:
  470.             # An HTTP/1.1 proxy is assumed to stay open unless
  471.             # explicitly closed.
  472.             conn = self.msg.getheader('connection')
  473.             if conn and "close" in conn.lower():
  474.                 return True
  475.             return False
  476.  
  477.         # Some HTTP/1.0 implementations have support for persistent
  478.         # connections, using rules different than HTTP/1.1.
  479.  
  480.         # For older HTTP, Keep-Alive indicates persistent connection.
  481.         if self.msg.getheader('keep-alive'):
  482.             return False
  483.  
  484.         # At least Akamai returns a "Connection: Keep-Alive" header,
  485.         # which was supposed to be sent by the client.
  486.         if conn and "keep-alive" in conn.lower():
  487.             return False
  488.  
  489.         # Proxy-Connection is a netscape hack.
  490.         pconn = self.msg.getheader('proxy-connection')
  491.         if pconn and "keep-alive" in pconn.lower():
  492.             return False
  493.  
  494.         # otherwise, assume it will close
  495.         return True
  496.  
  497.     def close(self):
  498.         if self.fp:
  499.             self.fp.close()
  500.             self.fp = None
  501.  
  502.     def isclosed(self):
  503.         # NOTE: it is possible that we will not ever call self.close(). This
  504.         #       case occurs when will_close is TRUE, length is None, and we
  505.         #       read up to the last byte, but NOT past it.
  506.         #
  507.         # IMPLIES: if will_close is FALSE, then self.close() will ALWAYS be
  508.         #          called, meaning self.isclosed() is meaningful.
  509.         return self.fp is None
  510.  
  511.     # XXX It would be nice to have readline and __iter__ for this, too.
  512.  
  513.     def read(self, amt=None):
  514.         if self.fp is None:
  515.             return ''
  516.  
  517.         if self._method == 'HEAD':
  518.             self.close()
  519.             return ''
  520.  
  521.         if self.chunked:
  522.             return self._read_chunked(amt)
  523.  
  524.         if amt is None:
  525.             # unbounded read
  526.             if self.length is None:
  527.                 s = self.fp.read()
  528.             else:
  529.                 s = self._safe_read(self.length)
  530.                 self.length = 0
  531.             self.close()        # we read everything
  532.             return s
  533.  
  534.         if self.length is not None:
  535.             if amt > self.length:
  536.                 # clip the read to the "end of response"
  537.                 amt = self.length
  538.  
  539.         # we do not use _safe_read() here because this may be a .will_close
  540.         # connection, and the user is reading more bytes than will be provided
  541.         # (for example, reading in 1k chunks)
  542.         s = self.fp.read(amt)
  543.         if self.length is not None:
  544.             self.length -= len(s)
  545.             if not self.length:
  546.                 self.close()
  547.         return s
  548.  
  549.     def _read_chunked(self, amt):
  550.         assert self.chunked != _UNKNOWN
  551.         chunk_left = self.chunk_left
  552.         value = []
  553.         while True:
  554.             if chunk_left is None:
  555.                 line = self.fp.readline()
  556.                 i = line.find(';')
  557.                 if i >= 0:
  558.                     line = line[:i] # strip chunk-extensions
  559.                 try:
  560.                     chunk_left = int(line, 16)
  561.                 except ValueError:
  562.                     # close the connection as protocol synchronisation is
  563.                     # probably lost
  564.                     self.close()
  565.                     raise IncompleteRead(''.join(value))
  566.                 if chunk_left == 0:
  567.                     break
  568.             if amt is None:
  569.                 value.append(self._safe_read(chunk_left))
  570.             elif amt < chunk_left:
  571.                 value.append(self._safe_read(amt))
  572.                 self.chunk_left = chunk_left - amt
  573.                 return ''.join(value)
  574.             elif amt == chunk_left:
  575.                 value.append(self._safe_read(amt))
  576.                 self._safe_read(2)  # toss the CRLF at the end of the chunk
  577.                 self.chunk_left = None
  578.                 return ''.join(value)
  579.             else:
  580.                 value.append(self._safe_read(chunk_left))
  581.                 amt -= chunk_left
  582.  
  583.             # we read the whole chunk, get another
  584.             self._safe_read(2)      # toss the CRLF at the end of the chunk
  585.             chunk_left = None
  586.  
  587.         # read and discard trailer up to the CRLF terminator
  588.         ### note: we shouldn't have any trailers!
  589.         while True:
  590.             line = self.fp.readline()
  591.             if not line:
  592.                 # a vanishingly small number of sites EOF without
  593.                 # sending the trailer
  594.                 break
  595.             if line == '\r\n':
  596.                 break
  597.  
  598.         # we read everything; close the "file"
  599.         self.close()
  600.  
  601.         return ''.join(value)
  602.  
  603.     def _safe_read(self, amt):
  604.         """Read the number of bytes requested, compensating for partial reads.
  605.  
  606.         Normally, we have a blocking socket, but a read() can be interrupted
  607.         by a signal (resulting in a partial read).
  608.  
  609.         Note that we cannot distinguish between EOF and an interrupt when zero
  610.         bytes have been read. IncompleteRead() will be raised in this
  611.         situation.
  612.  
  613.         This function should be used when <amt> bytes "should" be present for
  614.         reading. If the bytes are truly not available (due to EOF), then the
  615.         IncompleteRead exception can be used to detect the problem.
  616.         """
  617.         s = []
  618.         while amt > 0:
  619.             chunk = self.fp.read(min(amt, MAXAMOUNT))
  620.             if not chunk:
  621.                 raise IncompleteRead(''.join(s), amt)
  622.             s.append(chunk)
  623.             amt -= len(chunk)
  624.         return ''.join(s)
  625.  
  626.     def getheader(self, name, default=None):
  627.         if self.msg is None:
  628.             raise ResponseNotReady()
  629.         return self.msg.getheader(name, default)
  630.  
  631.     def getheaders(self):
  632.         """Return list of (header, value) tuples."""
  633.         if self.msg is None:
  634.             raise ResponseNotReady()
  635.         return self.msg.items()
  636.  
  637.  
  638. class HTTPConnection:
  639.  
  640.     _http_vsn = 11
  641.     _http_vsn_str = 'HTTP/1.1'
  642.  
  643.     response_class = HTTPResponse
  644.     default_port = HTTP_PORT
  645.     auto_open = 1
  646.     debuglevel = 0
  647.     strict = 0
  648.  
  649.     def __init__(self, host, port=None, strict=None,
  650.                  timeout=socket._GLOBAL_DEFAULT_TIMEOUT):
  651.         self.timeout = timeout
  652.         self.sock = None
  653.         self._buffer = []
  654.         self.__response = None
  655.         self.__state = _CS_IDLE
  656.         self._method = None
  657.         self._tunnel_host = None
  658.         self._tunnel_port = None
  659.         self._tunnel_headers = {}
  660.  
  661.         self._set_hostport(host, port)
  662.         if strict is not None:
  663.             self.strict = strict
  664.  
  665.     def _set_tunnel(self, host, port=None, headers=None):
  666.         """ Sets up the host and the port for the HTTP CONNECT Tunnelling.
  667.  
  668.         The headers argument should be a mapping of extra HTTP headers
  669.         to send with the CONNECT request.
  670.         """
  671.         self._tunnel_host = host
  672.         self._tunnel_port = port
  673.         if headers:
  674.             self._tunnel_headers = headers
  675.         else:
  676.             self._tunnel_headers.clear()
  677.  
  678.     def _set_hostport(self, host, port):
  679.         if port is None:
  680.             i = host.rfind(':')
  681.             j = host.rfind(']')         # ipv6 addresses have [...]
  682.             if i > j:
  683.                 try:
  684.                     port = int(host[i+1:])
  685.                 except ValueError:
  686.                     raise InvalidURL("nonnumeric port: '%s'" % host[i+1:])
  687.                 host = host[:i]
  688.             else:
  689.                 port = self.default_port
  690.             if host and host[0] == '[' and host[-1] == ']':
  691.                 host = host[1:-1]
  692.         self.host = host
  693.         self.port = port
  694.  
  695.     def set_debuglevel(self, level):
  696.         self.debuglevel = level
  697.  
  698.     def _tunnel(self):
  699.         self._set_hostport(self._tunnel_host, self._tunnel_port)
  700.         self.send("CONNECT %s:%d HTTP/1.0\r\n" % (self.host, self.port))
  701.         for header, value in self._tunnel_headers.iteritems():
  702.             self.send("%s: %s\r\n" % (header, value))
  703.         self.send("\r\n")
  704.         response = self.response_class(self.sock, strict = self.strict,
  705.                                        method = self._method)
  706.         (version, code, message) = response._read_status()
  707.  
  708.         if code != 200:
  709.             self.close()
  710.             raise socket.error("Tunnel connection failed: %d %s" % (code,
  711.                                                                     message.strip()))
  712.         while True:
  713.             line = response.fp.readline()
  714.             if line == '\r\n': break
  715.  
  716.  
  717.     def connect(self):
  718.         """Connect to the host and port specified in __init__."""
  719.         self.sock = socket.create_connection((self.host,self.port),
  720.                                              self.timeout)
  721.  
  722.         if self._tunnel_host:
  723.             self._tunnel()
  724.  
  725.     def close(self):
  726.         """Close the connection to the HTTP server."""
  727.         if self.sock:
  728.             self.sock.close()   # close it manually... there may be other refs
  729.             self.sock = None
  730.         if self.__response:
  731.             self.__response.close()
  732.             self.__response = None
  733.         self.__state = _CS_IDLE
  734.  
  735.     def send(self, str):
  736.         """Send `str' to the server."""
  737.         if self.sock is None:
  738.             if self.auto_open:
  739.                 self.connect()
  740.             else:
  741.                 raise NotConnected()
  742.  
  743.         # send the data to the server. if we get a broken pipe, then close
  744.         # the socket. we want to reconnect when somebody tries to send again.
  745.         #
  746.         # NOTE: we DO propagate the error, though, because we cannot simply
  747.         #       ignore the error... the caller will know if they can retry.
  748.         if self.debuglevel > 0:
  749.             print "send:", repr(str)
  750.         try:
  751.             blocksize=8192
  752.             if hasattr(str,'read') and not isinstance(str, array):
  753.                 if self.debuglevel > 0: print "sendIng a read()able"
  754.                 data=str.read(blocksize)
  755.                 while data:
  756.                     self.sock.sendall(data)
  757.                     data=str.read(blocksize)
  758.             else:
  759.                 self.sock.sendall(str)
  760.         except socket.error, v:
  761.             if v.args[0] == 32:      # Broken pipe
  762.                 self.close()
  763.             raise
  764.  
  765.     def _output(self, s):
  766.         """Add a line of output to the current request buffer.
  767.  
  768.         Assumes that the line does *not* end with \\r\\n.
  769.         """
  770.         self._buffer.append(s)
  771.  
  772.     def _send_output(self):
  773.         """Send the currently buffered request and clear the buffer.
  774.  
  775.         Appends an extra \\r\\n to the buffer.
  776.         """
  777.         self._buffer.extend(("", ""))
  778.         msg = "\r\n".join(self._buffer)
  779.         del self._buffer[:]
  780.         self.send(msg)
  781.  
  782.     def putrequest(self, method, url, skip_host=0, skip_accept_encoding=0):
  783.         """Send a request to the server.
  784.  
  785.         `method' specifies an HTTP request method, e.g. 'GET'.
  786.         `url' specifies the object being requested, e.g. '/index.html'.
  787.         `skip_host' if True does not add automatically a 'Host:' header
  788.         `skip_accept_encoding' if True does not add automatically an
  789.            'Accept-Encoding:' header
  790.         """
  791.  
  792.         # if a prior response has been completed, then forget about it.
  793.         if self.__response and self.__response.isclosed():
  794.             self.__response = None
  795.  
  796.  
  797.         # in certain cases, we cannot issue another request on this connection.
  798.         # this occurs when:
  799.         #   1) we are in the process of sending a request.   (_CS_REQ_STARTED)
  800.         #   2) a response to a previous request has signalled that it is going
  801.         #      to close the connection upon completion.
  802.         #   3) the headers for the previous response have not been read, thus
  803.         #      we cannot determine whether point (2) is true.   (_CS_REQ_SENT)
  804.         #
  805.         # if there is no prior response, then we can request at will.
  806.         #
  807.         # if point (2) is true, then we will have passed the socket to the
  808.         # response (effectively meaning, "there is no prior response"), and
  809.         # will open a new one when a new request is made.
  810.         #
  811.         # Note: if a prior response exists, then we *can* start a new request.
  812.         #       We are not allowed to begin fetching the response to this new
  813.         #       request, however, until that prior response is complete.
  814.         #
  815.         if self.__state == _CS_IDLE:
  816.             self.__state = _CS_REQ_STARTED
  817.         else:
  818.             raise CannotSendRequest()
  819.  
  820.         # Save the method we use, we need it later in the response phase
  821.         self._method = method
  822.         if not url:
  823.             url = '/'
  824.         str = '%s %s %s' % (method, url, self._http_vsn_str)
  825.  
  826.         self._output(str)
  827.  
  828.         if self._http_vsn == 11:
  829.             # Issue some standard headers for better HTTP/1.1 compliance
  830.  
  831.             if not skip_host:
  832.                 # this header is issued *only* for HTTP/1.1
  833.                 # connections. more specifically, this means it is
  834.                 # only issued when the client uses the new
  835.                 # HTTPConnection() class. backwards-compat clients
  836.                 # will be using HTTP/1.0 and those clients may be
  837.                 # issuing this header themselves. we should NOT issue
  838.                 # it twice; some web servers (such as Apache) barf
  839.                 # when they see two Host: headers
  840.  
  841.                 # If we need a non-standard port,include it in the
  842.                 # header.  If the request is going through a proxy,
  843.                 # but the host of the actual URL, not the host of the
  844.                 # proxy.
  845.  
  846.                 netloc = ''
  847.                 if url.startswith('http'):
  848.                     nil, netloc, nil, nil, nil = urlsplit(url)
  849.  
  850.                 if netloc:
  851.                     try:
  852.                         netloc_enc = netloc.encode("ascii")
  853.                     except UnicodeEncodeError:
  854.                         netloc_enc = netloc.encode("idna")
  855.                     self.putheader('Host', netloc_enc)
  856.                 else:
  857.                     try:
  858.                         host_enc = self.host.encode("ascii")
  859.                     except UnicodeEncodeError:
  860.                         host_enc = self.host.encode("idna")
  861.                     if self.port == self.default_port:
  862.                         self.putheader('Host', host_enc)
  863.                     else:
  864.                         self.putheader('Host', "%s:%s" % (host_enc, self.port))
  865.  
  866.             # note: we are assuming that clients will not attempt to set these
  867.             #       headers since *this* library must deal with the
  868.             #       consequences. this also means that when the supporting
  869.             #       libraries are updated to recognize other forms, then this
  870.             #       code should be changed (removed or updated).
  871.  
  872.             # we only want a Content-Encoding of "identity" since we don't
  873.             # support encodings such as x-gzip or x-deflate.
  874.             if not skip_accept_encoding:
  875.                 self.putheader('Accept-Encoding', 'identity')
  876.  
  877.             # we can accept "chunked" Transfer-Encodings, but no others
  878.             # NOTE: no TE header implies *only* "chunked"
  879.             #self.putheader('TE', 'chunked')
  880.  
  881.             # if TE is supplied in the header, then it must appear in a
  882.             # Connection header.
  883.             #self.putheader('Connection', 'TE')
  884.  
  885.         else:
  886.             # For HTTP/1.0, the server will assume "not chunked"
  887.             pass
  888.  
  889.     def putheader(self, header, value):
  890.         """Send a request header line to the server.
  891.  
  892.         For example: h.putheader('Accept', 'text/html')
  893.         """
  894.         if self.__state != _CS_REQ_STARTED:
  895.             raise CannotSendHeader()
  896.  
  897.         str = '%s: %s' % (header, value)
  898.         self._output(str)
  899.  
  900.     def endheaders(self):
  901.         """Indicate that the last header line has been sent to the server."""
  902.  
  903.         if self.__state == _CS_REQ_STARTED:
  904.             self.__state = _CS_REQ_SENT
  905.         else:
  906.             raise CannotSendHeader()
  907.  
  908.         self._send_output()
  909.  
  910.     def request(self, method, url, body=None, headers={}):
  911.         """Send a complete request to the server."""
  912.  
  913.         try:
  914.             self._send_request(method, url, body, headers)
  915.         except socket.error, v:
  916.             # trap 'Broken pipe' if we're allowed to automatically reconnect
  917.             if v.args[0] != 32 or not self.auto_open:
  918.                 raise
  919.             # try one more time
  920.             self._send_request(method, url, body, headers)
  921.  
  922.     def _send_request(self, method, url, body, headers):
  923.         # honour explicitly requested Host: and Accept-Encoding headers
  924.         header_names = dict.fromkeys([k.lower() for k in headers])
  925.         skips = {}
  926.         if 'host' in header_names:
  927.             skips['skip_host'] = 1
  928.         if 'accept-encoding' in header_names:
  929.             skips['skip_accept_encoding'] = 1
  930.  
  931.         self.putrequest(method, url, **skips)
  932.  
  933.         if body and ('content-length' not in header_names):
  934.             thelen=None
  935.             try:
  936.                 thelen=str(len(body))
  937.             except TypeError, te:
  938.                 # If this is a file-like object, try to
  939.                 # fstat its file descriptor
  940.                 import os
  941.                 try:
  942.                     thelen = str(os.fstat(body.fileno()).st_size)
  943.                 except (AttributeError, OSError):
  944.                     # Don't send a length if this failed
  945.                     if self.debuglevel > 0: print "Cannot stat!!"
  946.  
  947.             if thelen is not None:
  948.                 self.putheader('Content-Length',thelen)
  949.         for hdr, value in headers.iteritems():
  950.             self.putheader(hdr, value)
  951.         self.endheaders()
  952.  
  953.         if body:
  954.             self.send(body)
  955.  
  956.     def getresponse(self):
  957.         "Get the response from the server."
  958.  
  959.         # if a prior response has been completed, then forget about it.
  960.         if self.__response and self.__response.isclosed():
  961.             self.__response = None
  962.  
  963.         #
  964.         # if a prior response exists, then it must be completed (otherwise, we
  965.         # cannot read this response's header to determine the connection-close
  966.         # behavior)
  967.         #
  968.         # note: if a prior response existed, but was connection-close, then the
  969.         # socket and response were made independent of this HTTPConnection
  970.         # object since a new request requires that we open a whole new
  971.         # connection
  972.         #
  973.         # this means the prior response had one of two states:
  974.         #   1) will_close: this connection was reset and the prior socket and
  975.         #                  response operate independently
  976.         #   2) persistent: the response was retained and we await its
  977.         #                  isclosed() status to become true.
  978.         #
  979.         if self.__state != _CS_REQ_SENT or self.__response:
  980.             raise ResponseNotReady()
  981.  
  982.         if self.debuglevel > 0:
  983.             response = self.response_class(self.sock, self.debuglevel,
  984.                                            strict=self.strict,
  985.                                            method=self._method)
  986.         else:
  987.             response = self.response_class(self.sock, strict=self.strict,
  988.                                            method=self._method)
  989.  
  990.         response.begin()
  991.         assert response.will_close != _UNKNOWN
  992.         self.__state = _CS_IDLE
  993.  
  994.         if response.will_close:
  995.             # this effectively passes the connection to the response
  996.             self.close()
  997.         else:
  998.             # remember this, so we can tell when it is complete
  999.             self.__response = response
  1000.  
  1001.         return response
  1002.  
  1003.  
  1004. class HTTP:
  1005.     "Compatibility class with httplib.py from 1.5."
  1006.  
  1007.     _http_vsn = 10
  1008.     _http_vsn_str = 'HTTP/1.0'
  1009.  
  1010.     debuglevel = 0
  1011.  
  1012.     _connection_class = HTTPConnection
  1013.  
  1014.     def __init__(self, host='', port=None, strict=None):
  1015.         "Provide a default host, since the superclass requires one."
  1016.  
  1017.         # some joker passed 0 explicitly, meaning default port
  1018.         if port == 0:
  1019.             port = None
  1020.  
  1021.         # Note that we may pass an empty string as the host; this will throw
  1022.         # an error when we attempt to connect. Presumably, the client code
  1023.         # will call connect before then, with a proper host.
  1024.         self._setup(self._connection_class(host, port, strict))
  1025.  
  1026.     def _setup(self, conn):
  1027.         self._conn = conn
  1028.  
  1029.         # set up delegation to flesh out interface
  1030.         self.send = conn.send
  1031.         self.putrequest = conn.putrequest
  1032.         self.endheaders = conn.endheaders
  1033.         self.set_debuglevel = conn.set_debuglevel
  1034.  
  1035.         conn._http_vsn = self._http_vsn
  1036.         conn._http_vsn_str = self._http_vsn_str
  1037.  
  1038.         self.file = None
  1039.  
  1040.     def connect(self, host=None, port=None):
  1041.         "Accept arguments to set the host/port, since the superclass doesn't."
  1042.  
  1043.         if host is not None:
  1044.             self._conn._set_hostport(host, port)
  1045.         self._conn.connect()
  1046.  
  1047.     def getfile(self):
  1048.         "Provide a getfile, since the superclass' does not use this concept."
  1049.         return self.file
  1050.  
  1051.     def putheader(self, header, *values):
  1052.         "The superclass allows only one value argument."
  1053.         self._conn.putheader(header, '\r\n\t'.join(values))
  1054.  
  1055.     def getreply(self):
  1056.         """Compat definition since superclass does not define it.
  1057.  
  1058.         Returns a tuple consisting of:
  1059.         - server status code (e.g. '200' if all goes well)
  1060.         - server "reason" corresponding to status code
  1061.         - any RFC822 headers in the response from the server
  1062.         """
  1063.         try:
  1064.             response = self._conn.getresponse()
  1065.         except BadStatusLine, e:
  1066.             ### hmm. if getresponse() ever closes the socket on a bad request,
  1067.             ### then we are going to have problems with self.sock
  1068.  
  1069.             ### should we keep this behavior? do people use it?
  1070.             # keep the socket open (as a file), and return it
  1071.             self.file = self._conn.sock.makefile('rb', 0)
  1072.  
  1073.             # close our socket -- we want to restart after any protocol error
  1074.             self.close()
  1075.  
  1076.             self.headers = None
  1077.             return -1, e.line, None
  1078.  
  1079.         self.headers = response.msg
  1080.         self.file = response.fp
  1081.         return response.status, response.reason, response.msg
  1082.  
  1083.     def close(self):
  1084.         self._conn.close()
  1085.  
  1086.         # note that self.file == response.fp, which gets closed by the
  1087.         # superclass. just clear the object ref here.
  1088.         ### hmm. messy. if status==-1, then self.file is owned by us.
  1089.         ### well... we aren't explicitly closing, but losing this ref will
  1090.         ### do it
  1091.         self.file = None
  1092.  
  1093. try:
  1094.     import ssl
  1095. except ImportError:
  1096.     pass
  1097. else:
  1098.     class HTTPSConnection(HTTPConnection):
  1099.         "This class allows communication via SSL."
  1100.  
  1101.         default_port = HTTPS_PORT
  1102.  
  1103.         def __init__(self, host, port=None, key_file=None, cert_file=None,
  1104.                      strict=None, timeout=socket._GLOBAL_DEFAULT_TIMEOUT):
  1105.             HTTPConnection.__init__(self, host, port, strict, timeout)
  1106.             self.key_file = key_file
  1107.             self.cert_file = cert_file
  1108.  
  1109.         def connect(self):
  1110.             "Connect to a host on a given (SSL) port."
  1111.  
  1112.             sock = socket.create_connection((self.host, self.port), self.timeout)
  1113.             if self._tunnel_host:
  1114.                 self.sock = sock
  1115.                 self._tunnel()
  1116.             self.sock = ssl.wrap_socket(sock, self.key_file, self.cert_file)
  1117.  
  1118.     __all__.append("HTTPSConnection")
  1119.  
  1120.     class HTTPS(HTTP):
  1121.         """Compatibility with 1.5 httplib interface
  1122.  
  1123.         Python 1.5.2 did not have an HTTPS class, but it defined an
  1124.         interface for sending http requests that is also useful for
  1125.         https.
  1126.         """
  1127.  
  1128.         _connection_class = HTTPSConnection
  1129.  
  1130.         def __init__(self, host='', port=None, key_file=None, cert_file=None,
  1131.                      strict=None):
  1132.             # provide a default host, pass the X509 cert info
  1133.  
  1134.             # urf. compensate for bad input.
  1135.             if port == 0:
  1136.                 port = None
  1137.             self._setup(self._connection_class(host, port, key_file,
  1138.                                                cert_file, strict))
  1139.  
  1140.             # we never actually use these for anything, but we keep them
  1141.             # here for compatibility with post-1.5.2 CVS.
  1142.             self.key_file = key_file
  1143.             self.cert_file = cert_file
  1144.  
  1145.  
  1146.     def FakeSocket (sock, sslobj):
  1147.         warnings.warn("FakeSocket is deprecated, and won't be in 3.x.  " +
  1148.                       "Use the result of ssl.wrap_socket() directly instead.",
  1149.                       DeprecationWarning, stacklevel=2)
  1150.         return sslobj
  1151.  
  1152.  
  1153. class HTTPException(Exception):
  1154.     # Subclasses that define an __init__ must call Exception.__init__
  1155.     # or define self.args.  Otherwise, str() will fail.
  1156.     pass
  1157.  
  1158. class NotConnected(HTTPException):
  1159.     pass
  1160.  
  1161. class InvalidURL(HTTPException):
  1162.     pass
  1163.  
  1164. class UnknownProtocol(HTTPException):
  1165.     def __init__(self, version):
  1166.         self.args = version,
  1167.         self.version = version
  1168.  
  1169. class UnknownTransferEncoding(HTTPException):
  1170.     pass
  1171.  
  1172. class UnimplementedFileMode(HTTPException):
  1173.     pass
  1174.  
  1175. class IncompleteRead(HTTPException):
  1176.     def __init__(self, partial, expected=None):
  1177.         self.args = partial,
  1178.         self.partial = partial
  1179.         self.expected = expected
  1180.     def __repr__(self):
  1181.         if self.expected is not None:
  1182.             e = ', %i more expected' % self.expected
  1183.         else:
  1184.             e = ''
  1185.         return 'IncompleteRead(%i bytes read%s)' % (len(self.partial), e)
  1186.     def __str__(self):
  1187.         return repr(self)
  1188.  
  1189. class ImproperConnectionState(HTTPException):
  1190.     pass
  1191.  
  1192. class CannotSendRequest(ImproperConnectionState):
  1193.     pass
  1194.  
  1195. class CannotSendHeader(ImproperConnectionState):
  1196.     pass
  1197.  
  1198. class ResponseNotReady(ImproperConnectionState):
  1199.     pass
  1200.  
  1201. class BadStatusLine(HTTPException):
  1202.     def __init__(self, line):
  1203.         self.args = line,
  1204.         self.line = line
  1205.  
  1206. # for backwards compatibility
  1207. error = HTTPException
  1208.  
  1209. class LineAndFileWrapper:
  1210.     """A limited file-like object for HTTP/0.9 responses."""
  1211.  
  1212.     # The status-line parsing code calls readline(), which normally
  1213.     # get the HTTP status line.  For a 0.9 response, however, this is
  1214.     # actually the first line of the body!  Clients need to get a
  1215.     # readable file object that contains that line.
  1216.  
  1217.     def __init__(self, line, file):
  1218.         self._line = line
  1219.         self._file = file
  1220.         self._line_consumed = 0
  1221.         self._line_offset = 0
  1222.         self._line_left = len(line)
  1223.  
  1224.     def __getattr__(self, attr):
  1225.         return getattr(self._file, attr)
  1226.  
  1227.     def _done(self):
  1228.         # called when the last byte is read from the line.  After the
  1229.         # call, all read methods are delegated to the underlying file
  1230.         # object.
  1231.         self._line_consumed = 1
  1232.         self.read = self._file.read
  1233.         self.readline = self._file.readline
  1234.         self.readlines = self._file.readlines
  1235.  
  1236.     def read(self, amt=None):
  1237.         if self._line_consumed:
  1238.             return self._file.read(amt)
  1239.         assert self._line_left
  1240.         if amt is None or amt > self._line_left:
  1241.             s = self._line[self._line_offset:]
  1242.             self._done()
  1243.             if amt is None:
  1244.                 return s + self._file.read()
  1245.             else:
  1246.                 return s + self._file.read(amt - len(s))
  1247.         else:
  1248.             assert amt <= self._line_left
  1249.             i = self._line_offset
  1250.             j = i + amt
  1251.             s = self._line[i:j]
  1252.             self._line_offset = j
  1253.             self._line_left -= amt
  1254.             if self._line_left == 0:
  1255.                 self._done()
  1256.             return s
  1257.  
  1258.     def readline(self):
  1259.         if self._line_consumed:
  1260.             return self._file.readline()
  1261.         assert self._line_left
  1262.         s = self._line[self._line_offset:]
  1263.         self._done()
  1264.         return s
  1265.  
  1266.     def readlines(self, size=None):
  1267.         if self._line_consumed:
  1268.             return self._file.readlines(size)
  1269.         assert self._line_left
  1270.         L = [self._line[self._line_offset:]]
  1271.         self._done()
  1272.         if size is None:
  1273.             return L + self._file.readlines()
  1274.         else:
  1275.             return L + self._file.readlines(size)
  1276.  
  1277. def test():
  1278.     """Test this module.
  1279.  
  1280.     A hodge podge of tests collected here, because they have too many
  1281.     external dependencies for the regular test suite.
  1282.     """
  1283.  
  1284.     import sys
  1285.     import getopt
  1286.     opts, args = getopt.getopt(sys.argv[1:], 'd')
  1287.     dl = 0
  1288.     for o, a in opts:
  1289.         if o == '-d': dl = dl + 1
  1290.     host = 'www.python.org'
  1291.     selector = '/'
  1292.     if args[0:]: host = args[0]
  1293.     if args[1:]: selector = args[1]
  1294.     h = HTTP()
  1295.     h.set_debuglevel(dl)
  1296.     h.connect(host)
  1297.     h.putrequest('GET', selector)
  1298.     h.endheaders()
  1299.     status, reason, headers = h.getreply()
  1300.     print 'status =', status
  1301.     print 'reason =', reason
  1302.     print "read", len(h.getfile().read())
  1303.     print
  1304.     if headers:
  1305.         for header in headers.headers: print header.strip()
  1306.     print
  1307.  
  1308.     # minimal test that code to extract host from url works
  1309.     class HTTP11(HTTP):
  1310.         _http_vsn = 11
  1311.         _http_vsn_str = 'HTTP/1.1'
  1312.  
  1313.     h = HTTP11('www.python.org')
  1314.     h.putrequest('GET', 'http://www.python.org/~jeremy/')
  1315.     h.endheaders()
  1316.     h.getreply()
  1317.     h.close()
  1318.  
  1319.     try:
  1320.         import ssl
  1321.     except ImportError:
  1322.         pass
  1323.     else:
  1324.  
  1325.         for host, selector in (('sourceforge.net', '/projects/python'),
  1326.                                ):
  1327.             print "https://%s%s" % (host, selector)
  1328.             hs = HTTPS()
  1329.             hs.set_debuglevel(dl)
  1330.             hs.connect(host)
  1331.             hs.putrequest('GET', selector)
  1332.             hs.endheaders()
  1333.             status, reason, headers = hs.getreply()
  1334.             print 'status =', status
  1335.             print 'reason =', reason
  1336.             print "read", len(hs.getfile().read())
  1337.             print
  1338.             if headers:
  1339.                 for header in headers.headers: print header.strip()
  1340.             print
  1341.  
  1342. if __name__ == '__main__':
  1343.     test()
  1344.